/*
  small reusable signal-conditioning helpers to reduce noise
*/
#ifndef FILTERS_H
#define FILTERS_H

#include <Arduino.h>

// Exponential moving average 
class EMAFilter {
public:
  explicit EMAFilter(float alpha = 0.2f) : _alpha(alpha), _value(0), _initialized(false) {}

  float update(float sample) {
    if (!_initialized) {
      _value = sample;
      _initialized = true;
    } else {
      _value = _alpha * sample + (1.0f - _alpha) * _value;
    }
    return _value;
  }

  float get() const { return _value; }
  void reset() { _initialized = false; }

private:
  float _alpha;
  float _value;
  bool _initialized;
};

// Median-of-3: rejects a single spurious outlier 
class Median3Filter {
public:
  float update(float sample) {
    _buf[_idx] = sample;
    _idx = (_idx + 1) % 3;
    if (!_filled && _idx == 0) _filled = true;

    if (!_filled) return sample; // not enough history yet, pass through

    float a = _buf[0], b = _buf[1], c = _buf[2];
    return max(min(a, b), min(max(a, b), c)); 
  }

private:
  float _buf[3] = {0, 0, 0};
  uint8_t _idx = 0;
  bool _filled = false;
};

#endif 
